﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Reflection;
using Tree.Lifecycle;
using Tree.Injector;
using Tree.Container;
using System.Runtime.Serialization;
using Tree.Configuration;
using System.Configuration;
using System.Globalization;

namespace Tree.Factory.Impl
{
    public class ResolverImpl : IResolver
    {
        public Type ImplFor(Type type)
        {
            string interfaceName = string.Format("{0}.Impl.{1}Impl", type.Namespace, type.Name.Substring(1, type.Name.Length - 1));
            Type classType = TypeFrom(interfaceName);
            if (classType == null)
            {
                throw new TypeLoadException(String.Format("Could not find the type '{0}'.", interfaceName));
            }
            return classType;
        }

        public Type TypeFrom(string type)
        {
            Type classType = Type.GetType(type);
            if (classType == null)
            {
                foreach (Assembly assembly in AppDomain.CurrentDomain.GetAssemblies())
                {
                    classType = TypeFromFullname(type, assembly.GetName().Name);
                    if (classType != null)
                    {
                        break;
                    }
                }

                //if (Assembly.GetEntryAssembly() == null)
                //{
                //    foreach (Assembly assembly in AppDomain.CurrentDomain.GetAssemblies())
                //    {
                //        classType = TypeFromFullname(type, assembly.GetName().Name);
                //        if (classType != null)
                //        {
                //            break;
                //        }
                //    }
                //}
                //else
                //{
                //    classType = TypeFromFullname(type, Assembly.GetEntryAssembly().GetName().Name);
                //    if (classType != null)
                //    {
                //        return classType;
                //    }
                //    foreach (AssemblyName assembly in Assembly.GetEntryAssembly().GetReferencedAssemblies())
                //    {
                //        classType = TypeFromFullname(type, assembly.Name);
                //        if (classType != null)
                //        {
                //            break;
                //        }
                //    }
                //}
            }
            return classType;
        }

        public Type TypeFromFullname(string type, string name)
        {
            string implName = string.Format("{0}, {1}", type, name);
            return Type.GetType(implName);
        }
    }
}
